<?php

/**
* 微信类
*/
class Yjnic_Wechat_Basic{

	private $_configs = array();  
	private $_curl = null;
	
	function __construct($configs, $curl){
		$this->_configs = $configs;
		$this->_curl = $curl;
	}

	/**
	 * 获取access_token 
	 {"access_token":"ACCESS_TOKEN","expires_in":7200}
	 */
	public function getAccessToken(){		
		$url = 'https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid='.$this->_configs['app_id'].'&secret='.$this->_configs['app_secret'];		
		$ret = $this->_get($url);		
		return $ret;
	}

	/**
	 * 获取js api ticket
	 */
	public function getJsApiTicket($access_token){		
		$url = "https://api.weixin.qq.com/cgi-bin/ticket/getticket?type=jsapi&access_token={$access_token}";
		return $this->_get($url);		
	}

	/**
	 * 获取js 签名包
	 */
	public function getSignPackage($jsApiTicket){
		$protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off' || $_SERVER['SERVER_PORT'] == 443) ? "https://" : "http://";
		$url = trim( $protocol .$_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI'] );
		$timestamp = time();
	    $nonce_str = $this->_createNonceStr();

	    // 这里参数的顺序要按照 key 值 ASCII 码升序排序
	    $string = "jsapi_ticket={$jsapiTicket}&noncestr={$nonce_str}&timestamp={$timestamp}&url={$url}";

	    $signature = sha1($string);

	    $sign_package = array(
	      "appId"     => $this->_configs['app_id'],
	      "nonceStr"  => $nonce_str,
	      "timestamp" => $timestamp,
	      "url"       => $url,
	      "signature" => $signature,
	      "rawString" => $string
	    );
	    
	    return $sign_package; 
	}

	/**
	 * 创建 NonceStr
	 */
	public function _createNonceStr($length = 16){
		$chars = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789";
		$str = "";
		for ($i = 0; $i < $length; $i++) {
			$str .= substr($chars, mt_rand(0, strlen($chars) - 1), 1);
		}
		return $str;
	}

	/**
	 * 获取Auth access_token 
	 {
	    "access_token":"ACCESS_TOKEN",
	    "expires_in":7200,
	    "refresh_token":"REFRESH_TOKEN",
	    "openid":"OPENID",
	    "scope":"SCOPE",
	    "unionid": "o6_bmasdasdsad6_2sgVt7hMZOPfL"
	 }
	 */
	public function getAuthAccessToken($code=''){
		if (empty($code)) {
			throw new Yjnic_Wechat_Exception("Code Can Not Be Empty", 400);			
		}
		$url = 'https://api.weixin.qq.com/sns/oauth2/access_token?appid='.$this->_configs['app_id'].'&secret='.$this->_configs['app_secret'].'&code='.$code.'&grant_type=authorization_code';

		$ret = $this->_get($url);
		return $ret;
	}


	/**
	 * 验证是否来自微信的信息
	 */
	public function checkSignature($params){   
        // $signature = $_GET["signature"];
        // $timestamp = $_GET["timestamp"];
        // $nonce = $_GET["nonce"];
		$token = $this->_configs['token'];
		$tmpArr = array($token, $params['timestamp'], $params['nonce']);
        // use SORT_STRING rule
		sort($tmpArr, SORT_STRING);
		$tmpStr = implode( $tmpArr );
		$tmpStr = sha1( $tmpStr );
		
		if( $tmpStr == $params['signature'] ){
			return true;
		}else{
			return false;
		}
	}

	/**
	 * 获取用户信息
	{
	    "subscribe": 1, 
	    "openid": "o6_bmjrPTlm6_2sgVt7hMZOPfL2M", 
	    "nickname": "Band", 
	    "sex": 1, 
	    "language": "zh_CN", 
	    "city": "广州", 
	    "province": "广东", 
	    "country": "中国", 
	    "headimgurl":    "http://wx.qlogo.cn/mmopen/g3MonUZtNHkdmzicIlibx6iaFqAc56vxLSUfpb6n5WKSYVY0ChQKkiaJSgQ1dZuTOgvLLrhJbERQQ4eMsv84eavHiaiceqxibJxCfHe/0", 
	   "subscribe_time": 1382694957,
	   "unionid": " o6_bmasdasdsad6_2sgVt7hMZOPfL"
	   "remark": "",
	   "groupid": 0
	}
	 */
	public function getUserInfos($access_token, $openid){
		$url = 'https://api.weixin.qq.com/sns/userinfo?access_token='.$access_token.'&openid='.$openid.'&lang=zh_CN';
		return $this->_get($url);
	}

	/**
	 * 获取授权地址
	 */
	public function getScopeUrl($redirect_uri, $state = '123'){
		if ( !in_array($this->_configs['scope'], array('snsapi_base', 'snsapi_userinfo')) ) {
			throw new Yjnic_Wechat_Exception("Scope Must Be snsapi_base Or snsapi_userinfo", 400);			
		}
		$url = 'https://open.weixin.qq.com/connect/oauth2/authorize?appid='.$this->_configs['app_id'].'&redirect_uri='. urlencode($redirect_uri).'&response_type=code&scope='.$this->_configs['scope'].'&state='.$state.'#wechat_redirect';
		return $url;
	}

	private function _get($url, $params=array()){
		if (!empty($params)) {
			$query = http_build_query($params);
			if (strpos($url, '?')) {//如果已经存在 ?
				$url .= '&'.$query;
			}else{
				$url .= '?'.$query;
			}
		}		
		$ret = json_decode($this->_curl->get($url, 10), true);
		if ( isset($ret['errcode']) && $ret['errcode'] > 0 ) {
			throw new Yjnic_Wechat_Exception($ret['errmsg'], $ret['errcode']);			
		}
		return $ret;
	}

	private function _httpGet($url) {
		$curl = curl_init();
		curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
		curl_setopt($curl, CURLOPT_TIMEOUT, 500);
		// 为保证第三方服务器与微信服务器之间数据传输的安全性，所有微信接口采用https方式调用，必须使用下面2行代码打开ssl安全校验。
		// 如果在部署过程中代码在此处验证失败，请到 http://curl.haxx.se/ca/cacert.pem 下载新的证书判别文件。
		curl_setopt($curl, CURLOPT_SSL_VERIFYPEER, true);
		curl_setopt($curl, CURLOPT_SSL_VERIFYHOST, true);
		curl_setopt($curl, CURLOPT_URL, $url);

		$res = curl_exec($curl);
		curl_close($curl);

		return $res;
	}
}
